package lk.mrt.cse.wihidum.communicator;

import org.w3c.dom.Document;
import org.w3c.dom.NodeList;
import org.w3c.dom.Node;
import org.w3c.dom.Element;

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilder;

import java.io.File;
import java.util.ArrayList;

import lk.mrt.cse.wihidum.storage.*;

public class XMLReader
{

    String filePath = null;
    Topology topology = null;

    NeighbourBroker superUnit;
    NeighbourBroker peerUnit;
    NeighbourBroker subUnit;

    ArrayList<NeighbourBroker> superUnits = new ArrayList<NeighbourBroker>();
    ArrayList<NeighbourBroker> subUnits = new ArrayList<NeighbourBroker>();
    ArrayList<NeighbourBroker> peerUnits = new ArrayList<NeighbourBroker>();

    public XMLReader(String filePath) {
        this.filePath = filePath;
        topology = new Topology();
    }

    public Topology readXmlDocument() {
        try {
            File file = new File(filePath);
            DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
            DocumentBuilder db = dbf.newDocumentBuilder();
            Document doc = db.parse(file);
            doc.getDocumentElement().normalize();

            Element topologyElement = doc.getDocumentElement();

            NodeList topologyNameList = topologyElement.getElementsByTagName("TopologyName");
            Element topologyNameElement = (Element) topologyNameList.item(0);
            NodeList topologyName = topologyNameElement.getChildNodes();
            String strTopologyName = topologyName.item(0).getNodeValue();

            NodeList mySelfDataList = topologyElement.getElementsByTagName("MySelf");
            for (int i = 0; i < mySelfDataList.getLength(); i++) {
                Node node = mySelfDataList.item(i);
                if (node.getNodeType() == Node.ELEMENT_NODE && node != null) {
                    Element mySelfElement = (Element) node;

                    NodeList listID = mySelfElement.getElementsByTagName("ID");
                    Element idElement = (Element) listID.item(0);
                    NodeList id = idElement.getChildNodes();
                    topology.setMyId(id.item(0).getNodeValue());

                    NodeList listAddress = mySelfElement.getElementsByTagName("Address");
                    Element addressElement = (Element) listAddress.item(0);
                    NodeList address = addressElement.getChildNodes();
                    topology.setMyAddress(address.item(0).getNodeValue());

                    NodeList listRole = mySelfElement.getElementsByTagName("Role");
                    Element roleElement = (Element) listRole.item(0);
                    NodeList role = roleElement.getChildNodes();
                    topology.setMyRole(role.item(0).getNodeValue());
                }
            }

            NodeList listimmediateSU = topologyElement.getElementsByTagName("ImmediateSuperUnits").item(0).getChildNodes();
            for (int i = 0; i < listimmediateSU.getLength(); i++) {
                Node node = listimmediateSU.item(i);
                superUnit = new NeighbourBroker();

                if (node.getNodeType() == Node.ELEMENT_NODE && node != null) {
                    Element immediateSUElement = (Element) node;

                    NodeList listID = immediateSUElement.getElementsByTagName("ID");
                    Element idElement = (Element) listID.item(0);
                    NodeList id = idElement.getChildNodes();
                    superUnit.setBroekrID(id.item(0).getNodeValue());

                    NodeList listAddress = immediateSUElement.getElementsByTagName("Address");
                    Element addressElement = (Element) listAddress.item(0);
                    NodeList address = addressElement.getChildNodes();
                    superUnit.setAddress(address.item(0).getNodeValue());

                    superUnits.add(superUnit);
                }
            }


            NodeList listSecondarySU = topologyElement.getElementsByTagName("SecondarySuperUnits").item(0).getChildNodes();
            for (int i = 0; i < listSecondarySU.getLength(); i++) {
                Node node = listSecondarySU.item(i);

                if (node.getNodeType() == Node.ELEMENT_NODE && node != null) {
                    Element secondaySUElement = (Element) node;

                    NodeList listID = secondaySUElement.getElementsByTagName("ID");
                    Element idElement = (Element) listID.item(0);
                    NodeList id = idElement.getChildNodes();
                    String strID = id.item(0).getNodeValue();

                    NodeList listAddress = secondaySUElement.getElementsByTagName("Address");
                    Element addressElement = (Element) listAddress.item(0);
                    NodeList address = addressElement.getChildNodes();
                    String strAddress = address.item(0).getNodeValue();
                }
            }


            NodeList listSubUnits = topologyElement.getElementsByTagName("SubUnits").item(0).getChildNodes();
            for (int i = 0; i < listSubUnits.getLength(); i++) {
                Node node = listSubUnits.item(i);
                subUnit = new NeighbourBroker();

                if (node.getNodeType() == Node.ELEMENT_NODE && node != null) {
                    Element subUnitElement = (Element) node;

                    NodeList listID = subUnitElement.getElementsByTagName("ID");
                    Element idElement = (Element) listID.item(0);
                    NodeList id = idElement.getChildNodes();
                    subUnit.setBroekrID(id.item(0).getNodeValue());

                    NodeList listAddress = subUnitElement.getElementsByTagName("Address");
                    Element addressElement = (Element) listAddress.item(0);
                    NodeList address = addressElement.getChildNodes();
                    subUnit.setAddress(address.item(0).getNodeValue());

                    subUnits.add(subUnit);
                }

            }


            NodeList listPeerUnits = topologyElement.getElementsByTagName("PeerUnits").item(0).getChildNodes();
            for (int i = 0; i < listPeerUnits.getLength(); i++) {
                Node node = listPeerUnits.item(i);
                peerUnit = new NeighbourBroker();

                if (node.getNodeType() == Node.ELEMENT_NODE && node != null) {
                    Element peerUniElement = (Element) node;

                    NodeList listID = peerUniElement.getElementsByTagName("ID");
                    Element idElement = (Element) listID.item(0);
                    NodeList id = idElement.getChildNodes();
                    peerUnit.setBroekrID((id.item(0).getNodeValue()));

                    NodeList listAddress = peerUniElement.getElementsByTagName("Address");
                    Element addressElement = (Element) listAddress.item(0);
                    NodeList address = addressElement.getChildNodes();
                    peerUnit.setAddress(address.item(0).getNodeValue());

                    peerUnits.add(peerUnit);
                }

            }

            topology.setPeerUnits(peerUnits);
            topology.setSubUnits(subUnits);
            topology.setSuperUnits(superUnits);

            return topology;

        } catch (Exception e) {

            e.printStackTrace();
            return null;
        }

    }

}
